﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using Pahan.McuFusion.Common;
using Pahan.McuFusion.Common.Utils;
using Pahan.McuFusion.UI.Events;
using Pahan.McuFusion.UI.Workspaces;

namespace Pahan.McuFusion.UI.Scripting
{
    public sealed class ApplicationObject
    {
        #region Public Members

        public void NewWorkspace()
        {
            SafeInvoke(NewWorkspaceRequested, EventArgs.Empty);
        }

        public void SaveWorkspace()
        {
            SafeInvoke(SaveWorkspaceRequested, EventArgs.Empty);
        }

        public void SaveWorkspaceAs()
        {
            SafeInvoke(SaveWorkspaceAsRequested, EventArgs.Empty);
        }

        public void OpenWorkspace()
        {
            OpenWorkspace(null);
        }

        public void OpenWorkspace(String filename)
        {
            var e = new OpenWorkspaceEventArgs(new FileInfo(filename));
            SafeInvoke(OpenWorkspaceRequested, e);
        }

        public void OpenFile(MemoryClassInfo memoryClass)
        {
            var e = new MemoryOperationEventArgs(memoryClass);
            SafeInvoke(OpenFileRequested, e);
        }

        public void SaveFile(MemoryClassInfo memoryClass)
        {
            var e = new MemoryOperationEventArgs(memoryClass);
            SafeInvoke(SaveFileRequested, e);
        }

        public void ReadMemory(MemoryClassInfo memoryClass)
        {
            var e = new MemoryOperationEventArgs(memoryClass);
            SafeInvoke(ReadMemoryRequested, e);
        }

        public void WriteMemory(MemoryClassInfo memoryClass)
        {
            var e = new MemoryOperationEventArgs(memoryClass);
            SafeInvoke(WriteMemoryRequested, e);
        }

        public void EraseMemory(MemoryClassInfo memoryClass)
        {
            var e = new MemoryOperationEventArgs(memoryClass);
            SafeInvoke(EraseMemoryRequested, e);
        }

        public void Exit()
        {
            SafeInvoke(ExitRequested, EventArgs.Empty);
        }

        public Workspace CurrentWorkspace
        {
            get
            {
                var e = new DataTransferEventArgs<Workspace>();
                SafeInvoke(GetCurrentWorkspaceRequested, e);
                return e.Data;
            }
        }

        #endregion

        #region Private Members

        private void SafeInvoke<TEnventArgs>(Delegate handler, TEnventArgs e)
            where TEnventArgs : EventArgs
        {
            var h = handler;
            if (h != null)
            {
                h.DynamicInvoke(this, e);
            }
        }

        #endregion

        #region Internal Members

        /// <summary>
        /// Raised when the user performs some action to create a new workspace.
        /// </summary>
        internal event EventHandler NewWorkspaceRequested;

        /// <summary>
        /// Raised when the user wants to save the workspace to file.
        /// </summary>
        internal event EventHandler SaveWorkspaceRequested;

        /// <summary>
        /// Raised when the user wants to save the workspace to file.
        /// </summary>
        internal event EventHandler SaveWorkspaceAsRequested;

        /// <summary>
        /// Raised when the user wants to open a workspace from file.
        /// </summary>
        internal event OpenWorkspaceEventHandler OpenWorkspaceRequested;

        /// <summary>
        /// Raised when the user wants to read the content of the memory.
        /// </summary>
        internal event MemoryOperationEventHandler ReadMemoryRequested;

        /// <summary>
        /// Raised when the user wants to open the file with the firmware.
        /// </summary>
        internal event MemoryOperationEventHandler OpenFileRequested;

        /// <summary>
        /// Raised when the user wants to save the file with the firmware.
        /// </summary>
        internal event MemoryOperationEventHandler SaveFileRequested;

        /// <summary>
        /// Raised when the user wants to write the content of the file
        /// to the memory of the device.
        /// </summary>
        internal event MemoryOperationEventHandler WriteMemoryRequested;

        /// <summary>
        /// Raised when the user wants to erase the memory.
        /// </summary>
        internal event MemoryOperationEventHandler EraseMemoryRequested;

        /// <summary>
        /// Raised when the script wants to exit the application.
        /// </summary>
        internal event EventHandler ExitRequested;

        /// <summary>
        /// Raised when the script wants to get the workspace currently open in the application.
        /// </summary>
        internal event DataTransferEventHandler<Workspace> GetCurrentWorkspaceRequested;

        #endregion
    }
}
